﻿package com.bizmlib.ui.scrolling
{
	import flash.display.DisplayObject;
	import flash.display.DisplayObjectContainer;
	import flash.display.InteractiveObject;
	
	//import com.bizmlib.transitioning.*;
	import com.bizmlib.tram.*;
	
	
	[Event(name="scrollComplete", type="com.bizmlib.ui.scrolling.ScrollerEvent")]
	
	
	public class SmoothScroller extends SimpleScroller
	{
		protected var classTraveller:Class;
		
		protected var traveller:DisplayObject;
	
		//protected var transitionTravellerSlide:Transitioning;
		protected var transitionTravellerSlide:TraM;
	
	
		public function SmoothScroller()
		{
		}
	
		
		/**
		public function onUnload():void
		{
			super.onUnload();
	
			transitionTravellerSlide.complete();
	
			transitionTravellerSlide.removeEventListener(TransitioningEvent.EXECUTION, transitionTravellerSlideExecution);
			transitionTravellerSlide.removeEventListener(TransitioningEvent.COMPLETED, transitionTravellerSlideCompleted);
	
			delete transitionTravellerSlide;
			transitionTravellerSlide = null;
		}
		/**/
		override public function clean():void
		{
			super.clean();
			
			removeTraveller();
		}
	
	
		override protected function init():void
		{
			super.init();
		}
		override protected function createChildren():void
		{
			super.createChildren();
	
			slider.alpha = 0;
			
			createTraveller();
		}
		
		protected function createTraveller():void
		{
			var classTraveller:Class = classTraveller || classSlider;
			traveller = new classTraveller() as DisplayObject;
			addChild(traveller);
			
			var travellerAsInteractiveObject:InteractiveObject = traveller as InteractiveObject;
			if(travellerAsInteractiveObject)
			{
				travellerAsInteractiveObject.mouseEnabled = false;
			}
			
			var travellerAsDisplayObjectContainer:DisplayObjectContainer = traveller as DisplayObjectContainer;
			if(travellerAsDisplayObjectContainer)
			{
				travellerAsDisplayObjectContainer.mouseChildren = false;
			}
			/**
			transitionTravellerSlide = new TransitionDirectTransform
			(
				traveller,
				undefined,
				new TweenProcessorSpeeding(0, .4, .15, .5, Number.POSITIVE_INFINITY)
			);
			transitionTravellerSlide.addEventListener(TransitioningEvent.EXECUTION, transitionTravellerSlideExecution);
			transitionTravellerSlide.addEventListener(TransitioningEvent.COMPLETED, transitionTravellerSlideCompleted);
			/**/
			transitionTravellerSlide = new DirectTransform
			(
				traveller,
				undefined,
				new EngineAccelerate(0, .4, .15, .5, Number.POSITIVE_INFINITY)
			);
			transitionTravellerSlide.addEventListener(TraMEvent.EXECUTION, transitionTravellerSlideExecution);
			transitionTravellerSlide.addEventListener(TraMEvent.COMPLETED, transitionTravellerSlideCompleted);
		}
		protected function removeTraveller():void
		{
			if(contains(traveller))
			{
				removeChild(traveller);
			}
			
			if(transitionTravellerSlide.isRunning)
			{
				dispatchScrollCompleteEvent();
			}
			
			transitionTravellerSlide.stop();
			transitionTravellerSlide.removeEventListener(TraMEvent.EXECUTION, transitionTravellerSlideExecution);
			transitionTravellerSlide.removeEventListener(TraMEvent.COMPLETED, transitionTravellerSlideCompleted);
			transitionTravellerSlide.clean();
			transitionTravellerSlide = null;
			
			traveller = null;
		}
	
		override protected function updateWindow():void
		{
			//trace(this + ".updateWindow(" + arguments + ")");
			
			super.updateWindow();
			
			traveller.height = slider.height;
		}
		override protected function updatePosition():void
		{
			//trace(this + ".updatePosition(" + arguments + ")");
			//trace("positionOldValue=" + positionOldValue);
	
			super.updatePosition();
	
			//if(transitionTravellerSlide.isExecuting)
			//trace("state=" + state);
			if(canStartTraveller() && !isNaN(positionOldValue))
			{
				//trace(1 + "\t" + slider.y + "\t" + traveller.y);
				transitionTravellerSlide.start(undefined, {y:slider.y}, undefined, true);
				//trace("transitionTravellerSlide=" + transitionTravellerSlide);
			}
			//else if(!(isNaN(height) || isNaN(position) || (slider.y < 0) || (slider.y > height)))
			else
			{
				//trace(2 + "\t" + slider.y + "\t" + traveller.y);
				transitionTravellerSlide.stop();
				traveller.y = slider.y;
			}
//			else
//			{
//				transitionTravellerSlide.stop();
//				traveller.y = 0;
//			}
		}
		protected function canStartTraveller():Boolean
		{
			return Boolean(state);
		}
	
		override protected function sliderDrag(event:ScrollerEvent):void
		{
			//trace(this + ".sliderDrag(" + arguments + ")");
			//super.sliderDrag(event);
			transitionTravellerSlide.start(undefined, {y:slider.y});
			/**
			var localSliderTravel:Number = Math.max(0, trackHeight - slider._height);
			scrollTo(localSliderTravel==0?0:((slider.y - trackY1)/localSliderTravel), true);
			/**/
		}
	
		protected function transitionTravellerSlideExecution(event:TraMEvent):void
		{
			//trace(this + ".transitionTravellerSlideExecution(" + arguments + ")");
			scrollTo(calculatePositionForSliderY(traveller.y), true);
			/**
			var localSliderTravel:Number = Math.max(0, trackHeight - traveller.height);
			scrollTo(localSliderTravel==0?0:((traveller.y - trackY1)/localSliderTravel), true);
			/**/
		}
		protected function transitionTravellerSlideCompleted(event:TraMEvent):void
		{
			transitionTravellerSlide.engine.reStart();
			dispatchScrollCompleteEvent();
		}
		
		protected function dispatchScrollCompleteEvent():void
		{
			dispatchEvent(new ScrollerEvent(ScrollerEvent.SCROLL_COMPLETE));
		}
	}
}